package com.letv.whatslive.mongo.dao;

import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.letv.whatslive.common.utils.ObjectUtils;
import com.letv.whatslive.model.AssortContent;
import com.letv.whatslive.model.convert.AssortContentConvert;
import com.letv.whatslive.model.utils.ObjUtils;
import com.letv.whatslive.mongo.BaseDAO;
import com.mongodb.BasicDBList;
import com.mongodb.BasicDBObject;
import com.mongodb.DBCursor;
import com.mongodb.DBObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Repository;

import java.util.List;
import java.util.Map;

/**
 * Created by haojiayao on 16-08-02.
 */
@Repository
public class AssortContentDAO extends BaseDAO {

    private static final Logger logger = LoggerFactory.getLogger(AssortContentDAO.class);

    protected String collectionName = "assortContent";

    @Override
    protected void init() {
        super.init(this.collectionName);
    }

    @Override
    protected long getAutoIncrementId() {
        return idGenerate.generateId(this.collectionName);
    }

    /**
     * 插入记录
     *
     * @param assortContent
     * @return
     */
    public long insertAssortContent(AssortContent assortContent) {

        try {

            DBObject obj = AssortContentConvert.castAssortContentToDBObject(assortContent);
            return this.insert(obj);
        } catch (Exception e) {

            logger.error("insert assort content error!", e);
        }

        return 0L;
    }

    /**
     * 删除记录
     *
     * @param params
     */
    public void delAssortContent(Map<String, Object> params) {

        try {

            // dbObj 类似于 mysql 查询中的 where 关键字，可以添加各种搜索条件
            BasicDBObject query = getBasicDBObjectByParams(params);
            this.delete(query);
        } catch (Exception e) {

            logger.error("delete assort content by params error!", e);
        }
    }

    /**
     * 根据参数获取AssortContent
     *
     * @param params
     * @return
     */
    public AssortContent getAssortContent(Map<String, Object> params) {
        AssortContent assortContent = null;
        try {
            BasicDBObject query = getBasicDBObjectByParams(params);
            DBObject result = dbCollection.findOne(query);
            if (result != null) {
                assortContent = AssortContentConvert.castDBObjectToAssortContent(result);
            }
        } catch (Exception e) {
            logger.error("get assortContent by params error!", e);
        }
        return assortContent;
    }

    /**
     * 根据参数获取ProgramId的List
     *
     * @param params
     * @param orders
     * @param start
     * @param limit
     * @return
     */
    public List<Long> getProgramIdsByParams(Map<String, Object> params, Map<String, Object> orders, Integer start, Integer limit) {
        List<Long> result = Lists.newLinkedList();
        try {
            //dbObj 类似于 mysql 查询中的 where 关键字，可以添加各种搜索条件
            BasicDBObject query = getBasicDBObjectByParams(params);
            BasicDBObject order = getOrderParams(orders);
            Integer skip = start == null ? 0 : start;
            DBCursor cur = this.dbCollection.find(query).skip(skip)
                    .sort(order).limit(limit);
            while (cur.hasNext()) {
                DBObject dbObject = cur.next();
                result.add(ObjUtils.toLong(dbObject.get("programId")));
            }
        } catch (Exception e) {
            logger.error("get activity programIds by params error!", e);
        }
        return result;
    }

    /**
     * 根据分类ID和programList查询优先级
     *
     * @param assortId
     * @param programIds
     * @return
     */
    public Map<Long, Long> getPriorityByActivityIdAndProgramId(Long assortId, List<Long> programIds) {
        Map<Long, Long> result = Maps.newHashMap();
        try {
            BasicDBList values = new BasicDBList();
            for (Long id : programIds) {
                values.add(id);
            }
            BasicDBObject queryCondition = new BasicDBObject();
            queryCondition.put("assortId", assortId);
            queryCondition.put("programId", new BasicDBObject("$in", values));
            DBCursor cur = this.dbCollection.find(queryCondition);
            while (cur.hasNext()) {
                DBObject dbObject = cur.next();
                result.put(ObjUtils.toLong(dbObject.get("programId")), ObjUtils.toLong(dbObject.get("priority")));
            }
        } catch (Exception e) {
            logger.error("get activity programIds by params error!", e);
        }
        return result;
    }

    /**
     * 统计分类下的视频数
     *
     * @param params
     * @return
     */
    public Long countProgramIdsByParams(Map<String, Object> params) {
        Long result = 0L;
        try {
            //dbObj 类似于 mysql 查询中的 where 关键字，可以添加各种搜索条件
            BasicDBObject query = getBasicDBObjectByParams(params);
            result = this.dbCollection.count(query);
        } catch (Exception e) {
            logger.error("count activity programIds by params error!", e);
        }
        return result;
    }

    /**
     * 更新分类下的视频优先级
     *
     * @param queryParams
     * @param priority
     */
    public void updatePriority(Map<String, Object> queryParams, Long priority) {
        try {

            //dbObj 类似于 mysql 查询中的 where 关键字，可以添加各种搜索条件
            BasicDBObject query = getBasicDBObjectByParams(queryParams);
            DBObject update = new BasicDBObject();
            update.put("priority", priority);
            update.put("updateTime", System.currentTimeMillis());
            this.update(query, new BasicDBObject("$set", update));
        } catch (Exception e) {

            logger.error("update assort priority error!", e);
        }
    }

    /**
     * 根据查询参数Map获取查询条件对象
     *
     * @param params 查询参数Map
     * @return
     */
    private BasicDBObject getBasicDBObjectByParams(Map params) {

        //dbObj 类似于 mysql 查询中的 where 关键字，可以添加各种搜索条件
        BasicDBObject query = new BasicDBObject();// 新建查询基类对象 dbo
        if (params != null && params.size() > 0) {

            if (params.get("assortId") != null) {
                query.put("assortId", ObjectUtils.toLong(params.get("assortId")));
            }

            if (params.get("programId") != null) {
                query.put("programId", ObjectUtils.toLong(params.get("programId")));
            }
        }

        return query;
    }

    /**
     * 获取排序的BasicDBObject对象
     *
     * @param orders
     * @return
     */
    private BasicDBObject getOrderParams(Map<String, Object> orders) {

        BasicDBObject order = new BasicDBObject();
        if (null != orders && orders.size() > 0) {

            for (String key : orders.keySet()) {

                order.append(key, Integer.valueOf(String.valueOf(orders.get(key))));
            }
        } else {

            //默认按照创建时间排序
            order.append("startTime", -1);
        }
        return order;
    }

    /**
     * 更新分类详情信息
     *
     * @param params 更新参数
     */
    public void updateAssortContent(Map<String, Object> params) {

        DBObject query = getBasicDBObjectByParams(params);

        DBObject update = new BasicDBObject();
        Integer pType = ObjectUtils.toInteger(params.get("pType"));
        if (pType != null) {

            update.put("pType", pType);
        }

        Long priority = ObjectUtils.toLong(params.get("priority"));
        if (priority != null) {

            update.put("priority", priority);
        }

        update.put("updateTime", System.currentTimeMillis());

        this.update(query, new BasicDBObject("$set", update));
    }

    /**
     * 删除指定视频ID对应的分类详情
     *
     * @param programId 视频ID
     */
    public void deleteAssortContentByProgramId(Long programId) {

        BasicDBObject query = new BasicDBObject();
        query.put("programId", programId);

        this.dbCollection.remove(query);
    }

    /**
     * 根据指定视频ID查询对应分类详情
     *
     * @param programId 视频ID
     * @return
     */
    public List<AssortContent> getAssortContentListByProgramId(Long programId) {

        List<AssortContent> assortContentList = Lists.newArrayList();

        DBObject query = new BasicDBObject();
        query.put("programId", programId);

        DBObject order = new BasicDBObject();
        order.put("_id", -1);

        List<DBObject> dbObjectList = selectAll(query, order);
        if (dbObjectList != null) {

            for (DBObject dbObject : dbObjectList) {

                assortContentList.add(AssortContentConvert.castDBObjectToAssortContent(dbObject));
            }
        }

        return assortContentList;
    }
}
